use regex::Regex;
use std::fs;
use std::io::{self, BufReader, Read, Seek};
use std::path::Path;
use std::thread;
use std::time::Duration;

/// 执行 tail 命令
pub fn execute(args: &[String]) {
    if args.is_empty() {
        eprintln!("用法: tail [-n <行数>] [-f] <文件名>");
        return;
    }

    let mut line_count: usize = 10; // 默认行数
    let mut follow: bool = false; // 默认不跟踪
    let mut file_path: Option<&String> = None;

    // 解析命令行参数
    let mut iter = args.iter();
    while let Some(arg) = iter.next() {
        match arg.as_str() {
            "-f" => {
                follow = true;
            }
            "-n" => {
                if let Some(next) = iter.next() {
                    line_count = match next.parse::<usize>() {
                        Ok(n) => n,
                        Err(_) => {
                            eprintln!("错误: 行数必须是一个非负整数");
                            return;
                        }
                    };
                } else {
                    eprintln!("错误: '-n' 选项后需要指定行数");
                    return;
                }
            }
            _ => {
                // -{n}f 的处理， n代表数字, 使用正则匹配
                let re = Regex::new(r"-(\d+)(f)?").unwrap();
                if let Some(cap) = re.captures(arg) {
                    let num_str = cap.get(1).unwrap().as_str();
                    line_count = match num_str.parse::<usize>() {
                        Ok(n) => n,
                        Err(_) => {
                            eprintln!("错误: 行数必须是一个非负整数");
                            return;
                        }
                    };

                    // 检查是否有 -f 选项
                    if cap.get(2).is_some() {
                        follow = true;
                    }
                }

                // 假定第一个非选项参数是文件路径
                file_path = Some(arg);
            }
        }
    }

    // 检查文件路径是否提供
    let file_path = match file_path {
        Some(path) => Path::new(path),
        None => {
            eprintln!("错误: 需要指定文件名");
            return;
        }
    };

    // 检查文件是否存在
    if !file_path.exists() {
        eprintln!("错误: 文件 '{}' 不存在", file_path.display());
        return;
    }

    // 读取文件内容并输出最后 n 行
    if let Err(e) = tail_file(file_path, line_count, follow) {
        eprintln!("读取文件时出错: {}", e);
    }
}

/// 读取文件并输出最后 n 行或持续跟踪
fn tail_file(file_path: &Path, line_count: usize, follow: bool) -> io::Result<()> {
    let file = fs::OpenOptions::new().read(true).open(file_path)?;
    let mut reader = BufReader::new(file);

    // 读取文件内容
    let mut contents = String::new();
    reader.read_to_string(&mut contents)?;

    // 输出最后 n 行
    let lines: Vec<&str> = contents.lines().collect();
    let total_lines = lines.len();
    let start_index = total_lines.saturating_sub(line_count);

    for line in &lines[start_index..] {
        println!("{}", line);
    }

    // 如果跟踪，持续监视文件变化
    if follow {
        let mut last_size = contents.len();
        loop {
            thread::sleep(Duration::from_secs(1)); // 每隔一秒检查一次
            let current_size = fs::metadata(file_path)?.len() as usize;
            if current_size > last_size {
                // 读取新内容
                let mut new_contents = String::new();
                let mut file = fs::OpenOptions::new().read(true).open(file_path)?;
                file.seek(io::SeekFrom::Start(last_size as u64))?;
                file.read_to_string(&mut new_contents)?;

                // 输出新内容
                for line in new_contents.lines() {
                    println!("{}", line);
                }
                last_size = current_size; // 更新文件大小
            }
        }
    }

    Ok(())
}
